package com.glsc.ngateway.opmanage.service.deposit;

import com.glsc.ngateway.common.api.common.utils.DateUtil;
import com.glsc.ngateway.common.api.common.utils.PageUtil;
import com.glsc.ngateway.common.base.domain.mysql.opmanagemain.deposit.DepositoryBank;
import com.glsc.ngateway.common.base.domain.mysql.opmanagemain.deposit.DepositoryDayProfit;
import com.glsc.ngateway.common.base.repo.mysql.opmanagemain.deposit.DepositoryDayProfitRepository;
import com.glsc.ngateway.opmanage.dto.DepositoryDayProfitExcelDto;
import com.glsc.ngateway.opmanage.utils.SpecificationUtil;
import com.glsc.ngateway.opmanage.utils.report.ReportFileConfigEnum;
import com.glsc.ngateway.opmanage.utils.report.ReportFileUtil;
import com.glsc.ngateway.opmanage.utils.report.ReportUploadContext;
import com.google.common.collect.Lists;
import org.apache.commons.lang.StringUtils;
import org.springframework.data.domain.*;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.Assert;
import org.springframework.util.CollectionUtils;
import org.springframework.web.multipart.MultipartFile;

import javax.annotation.Resource;
import java.io.IOException;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Optional;

@Service
public class DepositoryDayProfitService {


    @Resource
    private DepositoryDayProfitRepository depositoryDayProfitRepository;

    @Resource
    private DepositoryBankService bankService;

    /**
     * 分页查找
     *
     * @param pageNo
     * @param pageSize
     * @param param
     * @return
     */
    public Page<DepositoryDayProfit> page(int pageNo, int pageSize, Map<String, Object> param) {
        Sort.Direction direction = Sort.Direction.DESC;
        String sort = "createTime";

        pageNo = PageUtil.initPageNo(pageNo);
        pageSize = PageUtil.initPageSize(pageSize);

        Pageable pageable = PageRequest.of(pageNo - 1, pageSize, direction, sort);
        Page<DepositoryDayProfit> page = depositoryDayProfitRepository.findAll(SpecificationUtil.buildSpecification(param, DepositoryDayProfit.class), pageable);

        return page;
    }

    /**
     * 计算保证金今日收益合计数据
     *
     * @return
     */
    public DepositoryDayProfit thisProfit() {
        DepositoryDayProfit condition = new DepositoryDayProfit();
        condition.setEffectDate(DateUtil.getNowDateString());
        List<DepositoryDayProfit> profitList = depositoryDayProfitRepository.findAll(Example.of(condition));

        DepositoryDayProfit res = DepositoryDayProfit.builder().bankBalance(BigDecimal.ZERO).interest(BigDecimal.ZERO).build();

        //查询当日备付金利息
        List<DepositoryDayProfit> beifujinDatas = depositoryDayProfitRepository.findAll(Example.of(DepositoryDayProfit.builder().bankName("备付金").effectDate(DateUtil.getNowDateString()).build()));
        if (!CollectionUtils.isEmpty(beifujinDatas)) {
            res.setBfjInterest(beifujinDatas.get(0).getInterest());
            res.setBfjBankBalance(beifujinDatas.get(0).getBankBalance());
        }

        if (CollectionUtils.isEmpty(profitList)) {
            return res;
        }

        for (DepositoryDayProfit item : profitList) {
            if (!"备付金".equals(item.getBankName())) {
                if (Objects.nonNull(item.getBankBalance())) {
                    res.setBankBalance(res.getBankBalance().add(item.getBankBalance()));
                }
                if (Objects.nonNull(item.getInterest())) {
                    res.setInterest(res.getInterest().add(item.getInterest()));
                }
            }
        }

        return res;
    }


    /**
     * 根据id查找
     *
     * @param id
     * @return
     */
    public DepositoryDayProfit findById(Integer id) {
        Optional<DepositoryDayProfit> optional = depositoryDayProfitRepository.findById(id);
        if (optional.isPresent()) {
            return optional.get();
        }
        return null;
    }

    /**
     * 保存
     *
     * @param obj
     * @return
     */
    public DepositoryDayProfit save(DepositoryDayProfit obj) {
        if (Objects.isNull(obj.getBankId())) {
            if (StringUtils.isNotBlank(obj.getBankName())) {
                DepositoryBank bank = bankService.findByName(obj.getBankName());
                if (Objects.nonNull(bank)) {
                    obj.setBankId(bank.getId());
                }
            }
        }

        if (Objects.nonNull(obj.getBankId())) {
            DepositoryBank bank = bankService.findById(obj.getBankId());
            obj.setBankName(bank.getBankName());
            //设置生效日期
            obj.setEffectDate(DateUtil.getNowDateString());
            //设置利率
            obj.setInterestRate(bank.getInterestRate());
            //计算当日利息 利率x银行余额/360
            obj.setInterest(bank.getInterestRate().multiply(obj.getBankBalance()).divide(BigDecimal.valueOf(36000), 2, RoundingMode.HALF_UP).setScale(2, RoundingMode.HALF_UP));
            if (!"备付金".equals(obj.getBankName())) {
                //计算存放比
                obj.setStowageRatio(obj.getBankBalance().divide(obj.getCounterBalance(), 4, RoundingMode.HALF_UP).multiply(BigDecimal.valueOf(100)));
                //计算客户结息 柜台余额0.21%/360 0.21%为预估客户结息利率
                obj.setCustomerInterest(obj.getCounterBalance().multiply(BigDecimal.valueOf(0.21)).divide(BigDecimal.valueOf(36000), 2, RoundingMode.HALF_UP).setScale(2, RoundingMode.HALF_UP));
                //计算息差收入
                obj.setSpreadIncome(obj.getInterest().subtract(obj.getCustomerInterest()));
                //季度利息汇总-暂不计算
                //obj.setQuarterInterest();
            }
        }

        obj.setDeleted("N");
        return depositoryDayProfitRepository.save(obj);
    }

    /**
     * 根据id删除
     *
     * @param id
     */
    public void delete(Integer id) {
        depositoryDayProfitRepository.deleteById(id);
    }


    @Transactional
    public ReportUploadContext<DepositoryDayProfitExcelDto, String> important(MultipartFile file) throws IOException {
        ReportUploadContext<DepositoryDayProfitExcelDto, String> context = ReportUploadContext.<DepositoryDayProfitExcelDto, String>builder().config(ReportFileConfigEnum.DEPOSITORY_DAY_PROFIT).file(file).build();

        ReportFileUtil.readSingleExcel(context);
        Assert.notEmpty(context.getReadRes(), "上传内容不可为空");


        List<DepositoryDayProfitExcelDto> readResList = context.getReadRes();
        if (CollectionUtils.isEmpty(readResList)) {
            return context;
        }

        for (DepositoryDayProfitExcelDto dto : readResList) {
            DepositoryDayProfit dayProfit = DepositoryDayProfit.builder().quarterInterest(dto.getQuarterInterest()).counterBalance(dto.getCounterBalance()).bankBalance(dto.getBankBalance()).build();
            DepositoryBank bank = bankService.findByName(dto.getBankName());
            if (Objects.nonNull(bank)) {
                dayProfit.setBankId(bank.getId());
            }
            save(dayProfit);
        }


        return context;
    }


}
